#include <stdio.h>
#include <stdlib.h>
#include "header/BTree.h"
#include "header/Librarian.h"

int main(){
    int option, res;
    BTree t = getBTree();
    BTree rdrt = getBTree();
    Hashptr tb = (Hashptr)malloc(sizeof(HashTable));
    tb->count = 0;
    tb->size = HASH_TABLE_SIZE;
    tb->rcd = (bookNodeptr *)malloc(sizeof(bookNodeptr) * tb->size);
    for(int i = 0;i < HASH_TABLE_SIZE;i++){
        tb->rcd[i] = NULL;
    }
    if(load(&t, &rdrt, tb)){
        printf("\n\n\n\n\n||->>                         load data success! Please enter to get the menu!");
        flush();
        system("cls");
    }
    menu();
    scanf("%d", &option);
    while(option != 13){
        switch (option){
            // 添加图书
            case 1:{
                int bookId;
                char name[30];
                char writer[30];
                int total;
                system("cls");
                flush(stdin);
                printf("the bookId is ?\n");
                scanf("%d", &bookId);
                printf("the book name is ?\n");
                scanf("%s", name);
                printf("the writer name is ?\n");
                scanf("%s", writer);
                printf("what is the total?\n");
                scanf("%d", &total);
                bookptr book = getBook(bookId, name, writer, total);
                system("cls");
                res = checkAndInsert(&t, tb, book->bookId, book);
                save(t, rdrt);
                if(res == 1){
                    printf("\n\n\n\n\n||->>                         insert book success! Please enter to get the menu!");
                }
                break;
            }
            // 添加借阅者
            case 2:{
                int userId;
                char readerName[20];
                system("cls");
                printf("the reader id is ?\n");
                scanf("%d", &userId);
                printf("the reader name is ?\n");
                scanf("%s", readerName);
                system("cls");
                readerptr reader = (readerptr)malloc(sizeof(struct reader));
                reader->readerId = userId;
                strcpy(reader->name, readerName);
                res = insertReader(&rdrt, reader);
                save(t, rdrt);
                if(res == 1){
                    printf("\n\n\n\n\n||->>                         insert reader success! Please enter to get the menu!");
                }
                break;
            }
            // 删除图书
            case 3:{
                system("cls");
                printf("input the bookId of which you want to delete:\n");
                int bookId;
                scanf("%d", &bookId);
                system("cls");
                resultptr result = searchBTree(t, bookId);
                if(result->tag == 0){
                    printf("not find the book(id is %d)\n", bookId);
                } else {
                    char bookName[50];
                    strcpy(bookName, ((bookptr)(result->pt->record[result->i]))->name);
                    removeHash(tb, (bookptr)((result)->pt->record[result->i]));
                    deleteBTree(&t, &(result->pt), result->i);
                    printf("\n\n\n\n\n||->>                         delete book success! Please enter to get the menu!");
                    time_t tm = time(NULL);
                    char time[25];
                    strftime(time, 25, "%Y-%m-%d %H:%M:%S", localtime(&tm));
                    char *msg = catchString(4, time, "      delete book ", bookName, "\n");
                    writeLog(msg);
                    free(msg);
                }
                save(t, rdrt);
                break;
            }
            // 更新图书
            case 4:{
                system("cls");
                printf("input the booId of which you want to update:\n");
                int updateId, updateCount;
                char name[50];
                char writer[50];
                scanf("%d", &updateId);
                resultptr updateResult =  searchBTree(t, updateId);
                if(updateResult->tag == 0){
                    printf("not find the book(id is %d)\n", updateId);
                } else {
                    system("cls");
                    printf("the book name is ?\n");
                    scanf("%s", name);
                    printf("the writer name is ?\n");
                    scanf("%s", writer);
                    printf("what is the total?\n");
                    scanf("%d", &updateCount);
                    if(updateBook(tb, (bookptr)(updateResult->pt->record[updateResult->i]), name, writer, updateCount)){
                        time_t tm = time(NULL);
                        char time[25],num[10];
                        itoa(updateId,num,10);
                        strftime(time, 25, "%Y-%m-%d %H:%M:%S", localtime(&tm));
                        char *msg = catchString(4, time, "      Update book ", num, "\n");
                        writeLog(msg);
                        free(msg);
                        printf("\n\n\n\n\n||->>                         update book success! Please enter to get the menu!");
                    } else {
                        printf("\n\n\n\n\n||->>                         update book failed! Please enter to get the menu!");
                    }
                }
                save(t, rdrt);
                break;
            }
            // 查看图书详情
            case 5:{
                system("cls");
                printf("please input the bookId of which you want to see detail:\n");
                int bookId;
                scanf("%d", &bookId);
                resultptr result =  searchBTree(t, bookId);
                if(result->tag == 0){
                    printf("not find the book(id is %d)\n", bookId);
                } else {
                    printBookDetail((bookptr)(result->pt->record[result->i]));
                }
                break;
            }
            // 打印索引结构
            case 6:{
                system("cls");
                printf("choose the book(B) or the reader(R): \n");
                char choose;
                flush(stdin);
                while((choose = getchar()) != 'B' && choose != 'b' && choose != 'R' && choose != 'r'){
                    flush();
                    printf("please input B or R \n");
                }
                printf("\n");
                BTree temp = (choose == 'B' || choose == 'b') ? t : rdrt;
                printBTree(temp);
                break;
            }
            // 查看某个作者的所有图书
            case 7:{
                system("cls");
                char writer[30];
                printf("input the writer you want to see \n");
                scanf("%s", writer);
                system("cls");
                printBookByWriter(tb, writer);
                break;
            }
            // 查看图书列表
            case 8:{
                system("cls");
                printAllBook(t);
                break;
            }
            // 查看借阅者列表
            case 9:{
                system("cls");
                printAllReader(rdrt);
                break;
            }
            // 销毁索引
            case 10:{
                system("cls");
                printf("if you want to destroy the index, which will remove all data(y/n):\n");
                char choose;
                flush(stdin);
                while((choose = getchar()) != 'Y' && choose != 'y' && choose != 'N' && choose != 'n'){
                    flush();
                    printf("please input y or n \n");
                }
                if(choose == 'Y' || choose == 'y'){
                    destroyBTree(t);
                    t = getBTree();
                    printf("\n\n\n\n\n||->>                         destroy successfully! \n");
                    save(t, rdrt);
                    time_t tm = time(NULL);
                    char time[25];
                    strftime(time, 25, "%Y-%m-%d %H:%M:%S", localtime(&tm));
                    char *msg = catchString(2,time,"      Destroy all.\n");
                    writeLog(msg);
                    free(msg);
                }
                break;
            }
            // 借书
            case 11:{
                system("cls");
                int bookId;
                int userId;
                printf("input the readerId: \n");
                scanf("%d", &userId);
                resultptr res = searchBTree(rdrt, userId);
                if(res->tag == 0){
                    printf("not find the reader(id is %d)\n", userId);
                    break;
                } else {
                    readerptr rdp = (readerptr)(res->pt->record[res->i]);
                    free(res);
                    flush(stdin);
                    printf("input bookId. until enter [ctrl+z] to complete \n");
                    while(~scanf("%d", &bookId)){
                        resultptr result = searchBTree(t, bookId);
                        if(result->tag == 0){
                            printf("not find the book(id is %d) \n", bookId);
                        } else {
                            if(borrowBook((bookptr)(result->pt->record[result->i]), rdp)){
                                time_t tm = time(NULL);
                                char time[25];
                                strftime(time, 25, "%Y-%m-%d %H:%M:%S", localtime(&tm));
                                char *msg = catchString(6, time, "      Borrow ", ((bookptr)(result->pt->record[result->i]))->name, "    readerId : ", int2str(userId),"\n");
                                writeLog(msg);
                                free(msg);
                                printf("borrow book successfully \n");
                            } else {
                                printf("borrow book failed \n");
                            }
                        }
                        free(result);
                        printf("input bookId. until enter [ctrl+z] to complete \n");
                    }
                }
                save(t, rdrt);
                break;
            }
            // 还书
            case 12:{
                system("cls");
                int userId;
                printf("input the readerId:\n");
                scanf("%d", &userId);

                printf("input bookId. until enter [ctrl+z] to complete \n");
                int bookId;
                int cnt;
                while(~(cnt = scanf("%d", &bookId))){
                    if(!cnt){
                        flush();
                        printf("illegal input \n");
                        continue;
                    }
                    resultptr result = searchBTree(t, bookId);
                    if(result->tag == 0){
                        printf("not find the book(id is %d) \n", bookId);
                    } else {
                        if(returnBook((bookptr)(result->pt->record[result->i]), userId)){
                            printf("return book successfully \n");
                            time_t tm = time(NULL);
                            char time[25];
                            strftime(time, 25, "%Y-%m-%d %H:%M:%S", localtime(&tm));
                            char *msg = catchString(6, time, "      Return ", ((bookptr)(result->pt->record[result->i]) )->name, "    readerId : ", int2str(userId),"\n");
                            writeLog(msg);
                            free(msg);
                        }
                    }
                    printf("input bookId. until enter [ctrl+z] to complete \n");
                }
                save(t, rdrt);
                break;
            }
                
            // 退出
            case 13:
                return 0;
            // input overflow option range
            default:{
                system("cls");
                printf("\n\n\n\n\n||->>                         illegal command! [enter] to continue to input order! \n");
                break;
            }
        }
        flush();
        getchar();
        system("cls");
        menu();
        scanf("%d", &option);
    }
    getchar();
    return 0;
}